home *** CD-ROM | disk | FTP | other *** search
/ SPACE 2 / SPACE - Library 2 - Volume 1.iso / misc / 40 / zap3.c < prev   
C/C++ Source or Header  |  1986-07-17  |  6KB  |  263 lines

  1. /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
  2. /* zap.c - version 1.0.3 */
  3.  
  4. #include "hack.h"
  5.  
  6. extern struct obj *mkobj_at();
  7. extern struct monst *makemon(), *mkmon_at(), youmonst;
  8. extern struct monst *bhit();
  9. extern char *exclam();
  10.  
  11. extern char *fl[];
  12.  
  13. /* type == -1: monster spitting fire at you */
  14. /* type == -1,-2,-3: bolts sent out by wizard */
  15. /* called with dx = dy = 0 with vertical bolts */
  16. buzz(type,sx,sy,dx,dy)
  17. register int type;
  18. register xchar sx,sy;
  19. register int dx,dy;
  20. {
  21.     int abstype = abs(type);
  22.     register char *fltxt = (type == -1) ? "blaze of fire" : fl[abstype];
  23.     struct rm *lev;
  24.     xchar range;
  25.     struct monst *mon;
  26.  
  27.     if(u.uswallow) {
  28.         register int tmp;
  29.  
  30.         if(type < 0) return;
  31.         tmp = zhit(u.ustuck, type);
  32.         pline("The %s rips into %s%s",
  33.             fltxt, mon_nam(u.ustuck), exclam(tmp));
  34.         return;
  35.     }
  36.     if(type < 0) pru();
  37.     range = rn1(7,7);
  38.     Tmp_at2(-1, dirlet(dx,dy));    /* open call */
  39.     while(range-- > 0) {
  40.         sx += dx;
  41.         sy += dy;
  42.         if((lev = &levl[sx][sy])->typ) Tmp_at2(sx,sy);
  43.         else {
  44.             int bounce = 0;
  45.             if(cansee(sx-dx,sy-dy))
  46.                 pline("The %s bounces!", fltxt);
  47.             if(ZAP_POS(levl[sx][sy-dy].typ))
  48.                 bounce = 1;
  49.             if(ZAP_POS(levl[sx-dx][sy].typ)) {
  50.                 if(!bounce || rn2(2)) bounce = 2;
  51.             }
  52.             switch(bounce){
  53.             case 0:
  54.                 dx = -dx;
  55.                 dy = -dy;
  56.                 continue;
  57.             case 1:
  58.                 dy = -dy;
  59.                 sx -= dx;
  60.                 break;
  61.             case 2:
  62.                 dx = -dx;
  63.                 sy -= dy;
  64.                 break;
  65.             }
  66.             Tmp_at2(-2,dirlet(dx,dy));
  67.             continue;
  68.         }
  69.         if(lev->typ == POOL && abstype == 1 /* fire */) {
  70.             range -= 3;
  71.             lev->typ = ROOM;
  72.             if(cansee(sx,sy)) {
  73.                 mnewsym(sx,sy);
  74.                 pline("The water evaporates.");
  75.             } else
  76.                 pline("You hear a hissing sound.");
  77.         }
  78.         if((mon = m_at(sx,sy)) &&
  79.            (type != -1 || mon->data->mlet != 'D')) {
  80.             wakeup(mon);
  81.             if(rnd(20) < 18 + mon->data->ac) {
  82.                 register int tmp = zhit(mon,abstype);
  83.                 if(mon->mhp < 1) {
  84.                     if(type < 0) {
  85.                         if(cansee(mon->mx,mon->my))
  86.                           pline("%s is killed by the %s!",
  87.                         Monnam(mon), fltxt);
  88.                         mondied(mon);
  89.                     } else
  90.                         killed(mon);
  91.                 } else
  92.                     hit(fltxt, mon, exclam(tmp));
  93.                 range -= 2;
  94.             } else
  95.                 miss(fltxt,mon);
  96.         } else if(sx == u.ux && sy == u.uy) {
  97.             nomul(0);
  98.             if(rnd(20) < 18+u.uac) {
  99.                 register int dam = 0;
  100.                 range -= 2;
  101.                 pline("The %s hits you!",fltxt);
  102.                 switch(abstype) {
  103.                 case 0:
  104.                     dam = d(2,6);
  105.                     break;
  106.                 case 1:
  107.                     if(Fire_resistance)
  108.                         pline("You don't feel hot!");
  109.                     else dam = d(6,6);
  110.                     if(!rn2(3))
  111.                         burn_scrolls();
  112.                     break;
  113.                 case 2:
  114.                     nomul(-rnd(25)); /* sleep ray */
  115.                     break;
  116.                 case 3:
  117.                     if(Cold_resistance)
  118.                         pline("You don't feel cold!");
  119.                     else dam = d(6,6);
  120.                     break;
  121.                 case 4:
  122.                     u.uhp = -1;
  123.                 }
  124.                 losehp(dam,fltxt);
  125.             } else pline("The %s whizzes by you!",fltxt);
  126.             stop_occupation();
  127.         }
  128.         if(!ZAP_POS(lev->typ)) {
  129.             int bounce = 0, rmn;
  130.             if(cansee(sx,sy)) pline("The %s bounces!",fltxt);
  131.             range--;
  132.             if(!dx || !dy || !rn2(20)){
  133.                 dx = -dx;
  134.                 dy = -dy;
  135.             } else {
  136.               if(ZAP_POS(rmn = levl[sx][sy-dy].typ) &&
  137.                 (IS_ROOM(rmn) || ZAP_POS(levl[sx+dx][sy-dy].typ)))
  138.                 bounce = 1;
  139.               if(ZAP_POS(rmn = levl[sx-dx][sy].typ) &&
  140.                 (IS_ROOM(rmn) || ZAP_POS(levl[sx-dx][sy+dy].typ)))
  141.                 if(!bounce || rn2(2))
  142.                     bounce = 2;
  143.  
  144.               switch(bounce){
  145.               case 0:
  146.                 dy = -dy;
  147.                 dx = -dx;
  148.                 break;
  149.               case 1:
  150.                 dy = -dy;
  151.                 break;
  152.               case 2:
  153.                 dx = -dx;
  154.                 break;
  155.               }
  156.               Tmp_at2(-2, dirlet(dx,dy));
  157.             }
  158.         }
  159.     }
  160.     Tmp_at2(-1,-1);
  161. }
  162.  
  163. zhit(mon,type)            /* returns damage to mon */
  164. register struct monst *mon;
  165. register type;
  166. {
  167.     register int tmp = 0;
  168.  
  169.     switch(type) {
  170.     case 0:            /* magic missile */
  171.         tmp = d(2,6);
  172.         break;
  173.     case -1:        /* Dragon blazing fire */
  174.     case 1:            /* fire */
  175.         if(index("Dg", mon->data->mlet)) break;
  176.         tmp = d(6,6);
  177.         if(index("YF", mon->data->mlet)) tmp += 7;
  178.         break;
  179.     case 2:            /* sleep*/
  180.         mon->mfroz = 1;
  181.         break;
  182.     case 3:            /* cold */
  183.         if(index("YFgf", mon->data->mlet)) break;
  184.         tmp = d(6,6);
  185.         if(mon->data->mlet == 'D') tmp += 7;
  186.         break;
  187.     case 4:            /* death*/
  188.         if(index(UNDEAD, mon->data->mlet)) break;
  189.         tmp = mon->mhp+1;
  190.         break;
  191.     }
  192.     mon->mhp -= tmp;
  193.     return(tmp);
  194. }
  195.  
  196. #define    CORPSE_I_TO_C(otyp)    (char) ((otyp >= DEAD_ACID_BLOB)\
  197.              ?  'a' + (otyp - DEAD_ACID_BLOB)\
  198.              :    '@' + (otyp - DEAD_HUMAN))
  199. revive(obj)
  200. register struct obj *obj;
  201. {
  202.     register struct monst *mtmp;
  203.  
  204.     if(obj->olet == FOOD_SYM && obj->otyp > CORPSE) {
  205.         /* do not (yet) revive shopkeepers */
  206.         /* Note: this might conceivably produce two monsters
  207.             at the same position - strange, but harmless */
  208.         mtmp = mkmon_at(CORPSE_I_TO_C(obj->otyp),obj->ox,obj->oy);
  209.         delobj(obj);
  210.     }
  211.     return(!!mtmp);        /* TRUE if some monster created */
  212. }
  213.  
  214. rloco(obj)
  215. register struct obj *obj;
  216. {
  217.     register tx,ty,otx,oty;
  218.  
  219.     otx = obj->ox;
  220.     oty = obj->oy;
  221.     do {
  222.         tx = rn1(COLNO-3,2);
  223.         ty = rn2(ROWNO);
  224.     } while(!goodpos(tx,ty));
  225.     obj->ox = tx;
  226.     obj->oy = ty;
  227.     if(cansee(otx,oty))
  228.         newsym(otx,oty);
  229. }
  230.  
  231. fracture_rock(obj)    /* fractured by pick-axe or wand of striking */
  232. register struct obj *obj;               /* no texts here! */
  233. {
  234.     /* unpobj(obj); */
  235.     obj->otyp = ROCK;
  236.     obj->quan = 7 + rn2(60);
  237.     obj->owt = weight(obj);
  238.     obj->olet = WEAPON_SYM;
  239.     if(cansee(obj->ox,obj->oy))
  240.         prl(obj->ox,obj->oy);
  241. }
  242.  
  243. burn_scrolls()
  244. {
  245.     register struct obj *obj, *obj2;
  246.     register int cnt = 0;
  247.  
  248.     for(obj = invent; obj; obj = obj2) {
  249.         obj2 = obj->nobj;
  250.         if(obj->olet == SCROLL_SYM) {
  251.             cnt++;
  252.             useup(obj);
  253.         }
  254.     }
  255.     if(cnt > 1) {
  256.         pline("Your scrolls catch fire!");
  257.         losehp(cnt, "burning scrolls");
  258.     } else if(cnt) {
  259.         pline("Your scroll catches fire!");
  260.         losehp(1, "burning scroll");
  261.     }
  262. }
  263.